home *** CD-ROM | disk | FTP | other *** search
/ Cream of the Crop 26 / Cream of the Crop 26.iso / program / ccdl150l.zip / IO / SSCANF.C < prev    next >
C/C++ Source or Header  |  1997-01-25  |  7KB  |  338 lines

  1. #include <stdio.h>
  2. #include <ctype.h>
  3. #include <string.h>
  4.  
  5. /* Floating point not supported */
  6.  
  7. char *skipspace(char *buf, int *width, int *skip)
  8. {
  9.     int i;
  10.     *skip = 0;
  11.     if (*width == 0) 
  12.         while (isspace(*buf))
  13.             buf++;
  14.     else {
  15.         for (i=*width; i >=0 && isspace(*buf); i--)
  16.             buf++;
  17.         if (i < 0) {
  18.             i = 0;
  19.             *skip = 1;
  20.         }
  21.         *width = i;
  22.     }
  23.     return buf;
  24. }
  25. static char *strtoone(char **buffer, const char *format, void *arg, int *count,int *chars)
  26. {
  27.     int ignore = 0;
  28.     int width = 0;
  29.     int size = 0;
  30.     int sgn = 0;
  31.     int c,skip=0,didit = 0;
  32.     unsigned cu;
  33.     char vals[132],*s;
  34.     int i;
  35.     vals[0] = 0;
  36.     if (*format == '*') {
  37.         ignore = 1;
  38.         format++;
  39.     }
  40.     if (isdigit(*format)) 
  41.         while (isdigit(*format))
  42.             width = width *10 + *format++ -'0';
  43.     if (*format == 'h' || *format == 'l' || *format == 'L')
  44.         size = *format++;
  45.     switch(*format++) {
  46.         case 'c':
  47.             (*chars)++;
  48.             c = *(*buffer)++;
  49.             (*chars)++;
  50.             if (c == 0)
  51.                 return 0;
  52.             if (!ignore) {
  53.                 (*count)++;
  54.                 *(char *)arg = (char)c;
  55.             }        
  56.             break;
  57.         case 'd':
  58.         case 'i':
  59.             *buffer = skipspace(*buffer,&width,&skip);
  60.             c = 0;
  61.             if (!skip) {
  62.                 if (*(*buffer) == '-') {
  63.                     sgn = 1;
  64.                     if (width)
  65.                         width--;
  66.                     (*buffer)++;
  67.                     (*chars)++;
  68.                 }
  69.                 else {
  70.                     if (*(*buffer) == '+') {
  71.                         (*buffer)++;
  72.                         if (width)
  73.                         width--;
  74.                         (*chars)++;
  75.                     }
  76.                 }
  77.                 if (width) {
  78.                     while(width && isdigit(**buffer)) {
  79.                         didit = 1;
  80.                         width--;
  81.                         c*=10;
  82.                         (*chars)++;
  83.                         c+=*(*buffer)++ - '0';
  84.                     }
  85.                     while (width && **buffer) {
  86.                         (*buffer)++;
  87.                         width--;
  88.                     }
  89.                 }
  90.                 else
  91.                     while(isdigit(**buffer)) {
  92.                         didit = 1;
  93.                         c*=10;
  94.                         (*chars)++;
  95.                         c+=*(*buffer)++ - '0';
  96.                     }
  97.                 if (sgn)
  98.                     c = -c;
  99.             }
  100.             if (!ignore) {
  101.                 (*count)+=didit;
  102.                 if (size == 'h') 
  103.                     *(short *)arg = (short)c;
  104.                 else
  105.                     *(int *)arg = c;
  106.             }
  107.             break;
  108.         case 'e':
  109.         case 'f':
  110.         case 'g': 
  111. #ifndef USE_FLOAT
  112. /*                fprintf(stderr,"FP not linked"); */
  113.                 if (!ignore)
  114.                     (*count)++;
  115. #endif
  116.                 break;    
  117.         case 'n':
  118.             *(int *)arg = (*count)++;
  119.             break;
  120.         case 'o':
  121.             *buffer = skipspace(*buffer,&width,&skip);
  122.             cu = 0;
  123.             if (!skip) {
  124.                 if (width) {
  125.                     while(width && isdigit(**buffer) && *(*buffer) < '8') {
  126.                         didit = 1;
  127.                         width--;
  128.                         cu*=8;
  129.                         (*chars)++;
  130.                         cu+=*(*buffer)++ - '0';
  131.                     }
  132.                     while (width && **buffer) {
  133.                         (*buffer)++;
  134.                         width--;
  135.                     }
  136.                 }
  137.                 else
  138.                     while(isdigit(**buffer) && *(*buffer) < '8') {
  139.                         didit = 1;
  140.                         cu*=10;
  141.                         (*chars)++;
  142.                         cu+=*(*buffer)++ - '0';
  143.                     }
  144.             }
  145.             if (!ignore) {
  146.                 (*count)+=didit;
  147.                 if (size == 'h') 
  148.                     *(unsigned short *)arg = (unsigned short)cu;
  149.                 else
  150.                     *(unsigned *)arg = cu;
  151.             }     
  152.             break;
  153.         case '[':
  154.             i = 0;
  155.             while (*format != 0 && *format != ']')
  156.                 vals[i++] = *format++;
  157.             vals[i] = 0;
  158.         case 's':
  159.             s = (char *)arg;
  160.             skip = width;
  161.             switch (vals[0]) {
  162.                 case 0:
  163.                     while (*(*buffer) != 0 && (width || !skip)) {
  164.                         if (!ignore)
  165.                             *s++ = *(*buffer)++;
  166.                         else
  167.                             (*buffer)++;
  168.                         width--;
  169.                         (*chars)++;
  170.                     }
  171.                     if (!ignore) {
  172.                         *s = 0;
  173.                         (*count) ++;
  174.                     }
  175.                     break;
  176.                 case '^':
  177.                     while (!strchr(&vals[1],*(*buffer)) && *(*buffer) != 0 && (width || !skip)) {
  178.                         if (!ignore)
  179.                             *s++ = *(*buffer)++;
  180.                         else
  181.                             (*buffer)++;
  182.                         width--;
  183.                         (*chars)++;
  184.                     }
  185.                     if (!ignore) {
  186.                         *s = 0;
  187.                         (*count) ++;
  188.                     }
  189.                     break;
  190.                     
  191.                 default:
  192.                     while (strchr(&vals[0],*(*buffer)) && *(*buffer) != 0 && (width || !skip)) {
  193.                         if (!ignore)
  194.                             *s++ = *(*buffer)++;
  195.                         else
  196.                             (*buffer)++;
  197.                         width--;
  198.                         (*chars)++;
  199.                     }
  200.                     if (!ignore) {
  201.                         *s = 0;
  202.                         (*count) ++;
  203.                     }
  204.                     break;
  205.             }
  206.             break;
  207.         case 'u':
  208.             *buffer = skipspace(*buffer,&width,&skip);
  209.             if (!skip) {
  210.                 cu = 0;
  211.                 if (width) {
  212.                     while(width && isdigit(**buffer)) {
  213.                         didit = 1;
  214.                         width--;
  215.                         cu*=10;
  216.                         (*chars)++;
  217.                         cu+=*(*buffer)++ - '0';
  218.                     }
  219.                     while (width && **buffer) {
  220.                         (*buffer)++;
  221.                         width--;
  222.                     }
  223.                 }
  224.                 else
  225.                     while(isdigit(**buffer)) {
  226.                         didit = 1;
  227.                         cu*=10;
  228.                         (*chars)++;
  229.                         cu+=*(*buffer)++ - '0';
  230.                     }
  231.             }
  232.             if (!ignore) {
  233.                 (*count)+=didit;
  234.                 if (size == 'h') 
  235.                     *(unsigned short *)arg = (unsigned short)cu;
  236.                 else
  237.                     *(unsigned *)arg = cu;
  238.             }
  239.             break;
  240.         case 'x':
  241.         case 'p':
  242.             cu = 0;
  243.             *buffer = skipspace(*buffer,&width,&skip);
  244.             if (!skip) {
  245.                 if (*(*buffer) == '0' && (*(*buffer+1) == 'X' || *(*buffer+1)== 'x')) {
  246.                     (*chars)+=2;
  247.                     *buffer+=2;
  248.                     if (width) {
  249.                         width-=2;
  250.                         if (width == 0)
  251.                             goto nox;
  252.                     }
  253.                 }
  254.                 if (width) {
  255.                     while(width && isxdigit(**buffer)) {
  256.                         didit = 1;
  257.                         width--;
  258.                         cu*=16;
  259.                         (*chars)++;
  260.                         cu+=*(*buffer) - '0';
  261.                         if (*(*buffer) >= 'a')
  262.                             cu -= 32;
  263.                         if (*(*buffer) >= 'A')
  264.                             cu -= 7;
  265.                     }
  266.                     while (width && **buffer) {
  267.                         (*buffer)++;
  268.                         width--;
  269.                     }
  270.                 }
  271.                 else
  272.                     while(isxdigit(**buffer)) {
  273.                         didit = 1;
  274.                         cu*=16;
  275.                         (*chars)++;
  276.                         cu+=*(*buffer) - '0';
  277.                         if (*(*buffer) >= 'a')
  278.                             cu -= 32;
  279.                         if (*(*buffer) >= 'A')
  280.                             cu -= 7;
  281.                         (*buffer)++;
  282.                     }
  283.             }
  284. nox:
  285.             if (!ignore) {
  286.                 (*count)+=didit;
  287.                 if (size == 'h') 
  288.                     *(unsigned short *)arg =(unsigned short) cu;
  289.                 else
  290.                     *(unsigned *)arg = cu;
  291.             }
  292.             break;
  293.         case '%':
  294.                 if (*format == **buffer)
  295.                     (*buffer)++;
  296.         default:
  297.             format++;
  298.     }
  299.     return format;
  300. }
  301.  
  302. int _scanf(char *buffer, const char *format,void *arglist)
  303. {
  304.     int i = 0,j=0;
  305.     int spacing = 1;
  306.     while (format && *format) {
  307.         while (*format != '%' && *format != 0) {
  308.             if (isspace(*format)) {
  309.                 if (spacing) {
  310.                     while (isspace(*buffer)!= 0) {
  311.                         if (*++buffer == 0)
  312.                             return(i);
  313.                         j++;
  314.                     }
  315.                     spacing = 0;
  316.                 }
  317.             }
  318.             else  {
  319.                 if (*format == *buffer)
  320.                     buffer++;
  321.                 spacing = 1;
  322.             }
  323.             format++;
  324.         }
  325.         spacing = 1;
  326.         if (*format && *++format)
  327.             format = strtoone(&buffer,format,((char **)arglist)[i],&i,&j);
  328.         if (!*buffer)
  329.             return i;
  330.     }
  331.     return(i);
  332. }
  333. /* should have a const but const isn't working right... */
  334.  
  335. int sscanf(char *buf, const char *format, ...)
  336. {
  337.     return _scanf(buf,format,(((char *)&format)+sizeof(char *)));
  338. }